package com.amarsoft.apot.config;

import org.springframework.beans.BeansException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.config.AutowireCapableBeanFactory;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import org.springframework.core.annotation.AnnotationUtils;
import org.springframework.stereotype.Component;

/**
 * @Description:
 * @title: ApplicationAwareUtil
 * @Author szh
 * @Date: 2021/12/27 16:10
 */
@Component
public class ApplicationAwareUtil implements ApplicationContextAware {

    private static ApplicationContext context;

    @Override
    public void setApplicationContext(ApplicationContext applicationContext)
            throws BeansException {
        context = applicationContext;
    }

    @Autowired
    public static ApplicationContext getContext() {
        return context;
    }

    /***
     * 根据class获取bean
     * 如果ioc内有则到ioc内获取
     * 否则 newInstance
     * @param clazz
     * @return
     * @throws IllegalAccessException
     * @throws InstantiationException
     */
    public static Object getProxyBean(Class clazz) throws IllegalAccessException, InstantiationException {
        Object bean = null;

        try {
            //如果有Component注解则到ioc内获取，取不到newInstance
            if (AnnotationUtils.findAnnotation(clazz, Component.class) != null) {
                bean = ApplicationAwareUtil.getContext().getBean(clazz);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        if (bean == null) {
            bean = clazz.newInstance();
            //注入spring依赖
            ApplicationAwareUtil.getAutowireFactory().autowireBean(bean);
        }
        return bean;
    }


    @Autowired
    AutowireCapableBeanFactory autowireCapableBeanFactory;


    public AutowireCapableBeanFactory getAutowireCapableBeanFactory() {
        return autowireCapableBeanFactory;
    }

    public static AutowireCapableBeanFactory getAutowireFactory() {

        if (context == null) {
            throw new RuntimeException("服务正在启动中，spring bean尚未初始化完成，RPC调用失败，请稍后调用！");
        }

        return context.getBean(ApplicationAwareUtil.class).getAutowireCapableBeanFactory();
    }


}
